package data;

import data.SynchronizedListQueue.theLock;

public class SynchronizedBoundedQueue implements MessageQueue {
	
	
	class theLock extends Object {}
	public theLock lockObject = new theLock();
	public theLock lockObject2 = new theLock();
  
  private final Message[] queue;
  private int in, size;


  public SynchronizedBoundedQueue(int max) {
    queue = new Message[max];
    in = 0;
    size = 0;
  }

  public boolean isFull() {
    synchronized(lockObject){
    	return size() >= queue.length;
    }
  }

  public void add(Message message) {
    synchronized(lockObject2){  
    	boolean interrupted = false;
    	while (isFull())
      	try {
       	 Thread.sleep(10);
        } catch (InterruptedException e) {
        	interrupted = true; 
        }
	    synchronized(lockObject){
	    	queue[in] = message;
	    	in = (in + 1) % queue.length;
	    	++size;
	    	if (interrupted)
	      	Thread.currentThread().interrupt();
	    }
    }
  }

  public boolean isEmpty() {
	return size() == 0;
  }

  public Message remove() {
   synchronized(lockObject){
	     if (isEmpty())
	       throw new IllegalStateException("empty buffer");
		int out = (in + queue.length - size) % queue.length;
		Message message = queue[out];
		--size;
		return message;
    }
  }

  public int size() {
    synchronized(lockObject){
    	return size;
    }
  }

}
